package com.czk.utlls;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.czk.pojo.*;
import com.czk.pojo.templateMessagepojo.First;
import com.czk.pojo.templateMessagepojo.Remark;
import com.czk.pojo.templateMessagepojo.location.*;
import com.czk.templatemessage.TemplateMessageOperate;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.springframework.mail.SimpleMailMessage;
import org.springframework.mail.javamail.JavaMailSenderImpl;

import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

/**
 * @Author:ChenZhangKun
 * @Date: 2021/8/2 16:18
 */
@Slf4j
public class MessageUtil {
    /**
     * 发送音乐信息
     *
     * @param map
     * @return
     */
    public static BaseMessage dealMusic(Map<String, String> map) {
        return new MusicMessage(map, new Music("周杰伦", "七里香", "xxxxx", "dsdsd", "dsdsd"));
    }

    /**
     * 发送视频消息的处理方法
     *
     * @param map
     * @return
     */
    public static BaseMessage dealVideo(Map<String, String> map) {
        return new VideoMessage(map, new Video("121", "45454", "4545"));
    }

    /**
     * 发送位置信息的处理方法
     *
     * @param map
     * @return
     */
    public static BaseMessage dealLocation(Map<String, String> map) {
        // 拿到位置信息
        // {Location_X=30.788883, CreateTime=1628663745, Location_Y=103.892175, Label=四川省成都市郫都区创智南四路, Scale=15, ToUserName=gh_b1836e96d5e7,
        // FromUserName=o365s57rVcua532rJ9zD2US518Wk, MsgType=location, MsgId=23316861009828162}
        // 发送模板消息
        PersonLocation personLocation = new PersonLocation();
        personLocation.setFirst(new First("已经成功获取您的地理信息", "#17177"));
        // 获取用户名
        GetUserInfoUtil getUserInfoUtil = ApplicationContextHolder.getBean(GetUserInfoUtil.class);
        // 拿到用户
        String user;
        String userId = null;
        try {
            // 用户id
            userId = map.get("FromUserName");
            log.info("【用户id{}】", userId);
            user = getUserInfoUtil.getUser(userId);
            log.info("用户信息{}", user);
            // 转为json
            JSONObject jsonObject = JSONObject.parseObject(user);
            // 拿到名称
            String o = jsonObject.getString("nickname");
            personLocation.setName(new Name(o, "#fff000"));
        } catch (IOException e) {
            e.printStackTrace();
        }
        personLocation.setLatitude(new Latitude(map.get("Location_X"), "#1f1f1f"));
        personLocation.setLongitude(new Longitude(map.get("Location_Y"), "#1f1f1f"));
        personLocation.setLocation(new Location(map.get("Label"), "#17177"));
        personLocation.setRemark(new Remark("感谢使用", "#fff000"));
        // 发送
        TemplateMessageOperate templateMessageOperate = ApplicationContextHolder.getBean(TemplateMessageOperate.class);
        templateMessageOperate.sendLocationTemplateMessage(personLocation, userId);
        return new TextMessage(map, "地址位置接收成功");
    }

    /**
     * 处理短视频的方法
     *
     * @param map
     * @return
     */
    public static BaseMessage dealShortVideo(Map<String, String> map) {
        return new BaseMessage(map);
    }

    /**
     * 处理语音信息的方法
     *
     * @param map
     * @return
     */
    public static BaseMessage dealVoice(Map<String, String> map) {
        // 拿到认识的结果
        // Format=amr, MediaId=4PKhA3xo5k6AWPpkSze9D29hD_evRBXWw3t3HFnH7ggI1Jc4UkR5QupxW-dS3C1d, CreateTime=1628663644, ToUserName=gh_b1836e96d5e7,
        // FromUserName=o365s57rVcua532rJ9zD2US518Wk, MsgType=voice, MsgId=6995057087164186624, Recognition=你好。}
        String recognition = map.get("Recognition");
        return new TextMessage(map, recognition);
    }

    /**
     * 处理图片信息的方法
     *
     * @param map
     * @return
     */
    public static BaseMessage dealImage(Map<String, String> map) {
        // 进行图片识别
        // 调用百度的图像识别接口
        log.info("调用图片的识别接口");
        String path = map.get("PicUrl");
        JSONObject jsonObject = BaiDuAi.codeRecord(path);
        // 拿到结果
        JSONArray jsonArray = jsonObject.getJSONArray("words_result");
        // 遍历
        Iterator<Object> iterator = jsonArray.iterator();
        StringBuilder builder = new StringBuilder();
        while (iterator.hasNext()) {
            Object next = iterator.next();
            JSONObject json = (JSONObject) next;
            builder.append(json.getString("words"));
        }
        return new ImageMessage(map, builder.toString());
    }

    /**
     * 处理文字信息
     *
     * @param map
     * @return
     */
    public static BaseMessage dealText(Map<String, String> map) {
        log.info("【发送的内容是{}】", map.get("Content"));
        if (map.get("Content").equals("图文")) {
            return dealArticle(map);
        }
        if (map.get("Content").equals("登录")) {
            // 获取未关注用的code，用于换区access_token
            String url = "https://open.weixin.qq.com/connect/oauth2/authorize?appid=APPID&redirect_uri=REDIRECT_URI&response_type=code&scope=SCOPE&state=STATE#wechat_redirect";
            url = url.replace("APPID", "wx1c59434afb49c9c5").replace("REDIRECT_URI", "http://czk.free.idcfengye.com/wechat/get/user").replace("SCOPE", "snsapi_userinfo");
            return new TextMessage(map, "点击<a href=\"" + url + "\">这里</a>登录");
        }
        if (map.get("Content").equals("订阅消息")) {
            // 获取推送订阅消息
            String url = "https://mp.weixin.qq.com/mp/subscribemsg?action=get_confirm&appid=wxaba38c7f163da69b&scene=1&template_id=1uDxHNXwYQfBmXOfPJcjAS3FynHArD8aWMEFNRGSbCc&redirect_url=http%3a%2f%2fsupport.qq.com&reserved=test#wechat_redirect";
            // 替换 appid 重定向地址 和模板消息id
            url = url.replace("appid", "wx1c59434afb49c9c5").replace("1uDxHNXwYQfBmXOfPJcjAS3FynHArD8aWMEFNRGSbCc", "45ekMzrSnNZPxTteky8kEfBjzqkaJLtvyHQYxHKdFPs")
                    .replace("http%3a%2f%2fsupport.qq.com", "http://czk.free.idcfengye.com/wechat/get/push");
            return new TextMessage(map, "点击<a href=\"" + url + "\">这里</a>获取消息推送能力");

        }
        if (map.get("Content").startsWith("翻译")) {
            // 翻译接口
            TokenUtil tokenUtil = ApplicationContextHolder.getBean(TokenUtil.class);
            // 地址
            String url = "http://api.weixin.qq.com/cgi-bin/media/voice/translatecontent?access_token=ACCESS_TOKEN&lfrom=LFROM&lto=LTO";
            url = url.replace("ACCESS_TOKEN", tokenUtil.getToken().getAccessToken()).replace("LFROM", "zh_CN").replace("LTO", "en_US");
            // 带文件的post形式
            String originContent = "经过一个月阻击新冠肺炎疫情的奋战，江苏南京市全域已降为低风险地区，扬州市社区层面风险已基本消除。8月26日，国务院联防联控机制综合组江苏工作组人员全部撤离江苏。\n" +
                    "\n" +
                    "7月20日，南京禄口国际机场暴发与境外输入关联疫情，根据国务院联防联控机制要求，国务院联防联控机制综合组于7月23日派出雷海潮任组长、沈洪兵任副组长的工作组赴江苏省指导疫情应急处置工作。工作组先后在南京、扬州等地开展指导工作。协助当地组织全员核酸筛查，南京市和扬州市分别实现了两天一轮次和一天一轮次的高频筛查；迅速查明两市传染源头和感染路径；除中高风险地区外，增划封闭管控重点区域，防止疫情扩散蔓延；指导开展南京禄口国际机场等重点场所终末消毒，消除传染隐患；组织南京和扬州对密接人员应隔尽隔、集中隔离；指导无疫小区创建，在村居建立公共卫生委员会，改善基层卫生治理；坚持中西医并重，开展规范化同质化诊疗，深入指导院感防控，重症危重症患者已清零。\n" +
                    "\n" +
                    "南京禄口国际机场疫情是一起德尔塔变异毒株输入国内引发的突发公共卫生事件，是继武汉疫情之后波及国内范围最广、感染人数较多的疫情。\n" +
                    "\n" +
                    "事实证明，国内去年以来形成的新冠肺炎疫情处置经验和方法完全能够应对德尔塔毒株。在坚持基本经验和处置方法的基础上，也需要总结反思，与时俱进，不断优化丰富完善抗疫措施与技术，把外防输入、内防反弹的总体要求落到实处。";
            String content = WeChatUtil.post(url, originContent);
            // 转为json
            JSONObject jsonObject = JSONObject.parseObject(content);
            log.info("【content={}】", content);
            // 拿到翻译前
            if (jsonObject != null) {
                String from_content = jsonObject.getString("from_content");
                String to_content = jsonObject.getString("to_content");
                // 返回消息
                return new TextMessage(map, "范翻译前内容:" + from_content + "\r\n翻译后内容" + to_content);
            } else {
                return new TextMessage(map, "翻译失败");
            }

        }
        TextMessage textMessage = new TextMessage(map, "你好");
        return textMessage;
    }

    /**
     * 返回图文信息的方法
     *
     * @param map
     * @return
     */
    public static BaseMessage dealArticle(Map<String, String> map) {
        Article article = new Article("百度", "百度地址", "http://mmbiz.qpic.cn/mmbiz_jpg/TgMAfkPAx76UXVQFeZvXlOKacmJ20l6aQ5ibwm97lgicO1US9wZYahFIKJJreD1za5dYHVreqy87M6ySsEqtbcxw/0", "http://www.baidu.com");
        List<Article> list = new ArrayList<>();
        list.add(article);
        return new NewsMessage(map, "1", list);
    }

    /**
     * 处理事件推送的方法
     *
     * @param map
     * @return
     */
    public static BaseMessage dealEvent(Map<String, String> map) {
        try {
            String event = map.get("Event");
            log.info("【event类型{}】", event);
            switch (event) {
                case "CLICK":
                    return dealEventClick(map);
                case "VIEW":
                    return dealEventView(map);
                case "LOCATION":
                    return dealEventLocation(map);
                case "subscribe":
                    return dealWithSubscribe(map);
                case "unsubscribe":
                    return dealWithUnSubscribe(map);
                case "SCAN":
                    return dealWithScan(map);
                default:
                    return new TextMessage(map, "不支持的事件类型");
            }
        } catch (Exception ex) {
            ex.printStackTrace();
        }
        return null;
    }

    /**
     * 处理二维码扫描事件
     *
     * @param map
     * @return
     */
    private static BaseMessage dealWithScan(Map<String, String> map) {
        // 拿到ticket
        System.out.println(map.get("Ticket"));
        // 拿到事件序号
        String eventKey = map.get("EventKey");
        //
        log.info("【事件序号是{}】", eventKey);
        switch (eventKey) {
            case "1":
                return EventKeyDealUtil.dealWithEventKeyOne(map);
            case "2":
                return EventKeyDealUtil.dealWithEventKeySecond(map);
            default:
                return new TextMessage(map, "不支持的事件序号");
        }
    }

    /**
     * 处理取消关注事件
     * 发送邮件给主人
     *
     * @param map
     * @return
     */
    @SneakyThrows
    private static BaseMessage dealWithUnSubscribe(Map<String, String> map) {
        JavaMailSenderImpl javaMailSender = ApplicationContextHolder.getBean(JavaMailSenderImpl.class);
        // 拿到用户
        GetUserInfoUtil getUserInfoUtil = ApplicationContextHolder.getBean(GetUserInfoUtil.class);
        // 拿到用户=》此时用户未能关注公众号，不能直接获取信息，需要走位关注的人接口获取用户信息
        String user = getUserInfoUtil.getUser(map.get("FromUserName"));
        //
        JSONObject jsonObject = JSONObject.parseObject(user);
        log.info("【用户信息{}】", jsonObject);
        //
        String nickname = jsonObject.getString("nickname");
        // 发送邮件
        SimpleMailMessage simpleMailMessage = new SimpleMailMessage();
        simpleMailMessage.setSubject("用户取消关注");
        simpleMailMessage.setText("用户名称: " + nickname + "\n" + "微信号：" + map.get("FromUserName") + "\n" + "取消关注了，请及时跟踪");
        simpleMailMessage.setFrom("1052031630@qq.com");
        simpleMailMessage.setTo("528402297@qq.com");
        javaMailSender.send(simpleMailMessage);
        log.info("【邮件发送成功】");
        return new TextMessage(map, "发送邮件成功");
    }

    /**
     * 处理订阅事件
     *
     * @param map
     * @return
     */
    @SneakyThrows
    private static BaseMessage dealWithSubscribe(Map<String, String> map) {
        GetUserInfoUtil userInfoUtil = ApplicationContextHolder.getBean(GetUserInfoUtil.class);
        // 拿到用户
        String user = userInfoUtil.getUser(map.get("FromUserName"));
        // 转为json
        JSONObject jsonObject = JSONObject.parseObject(user);
        // 拿到用户名
        String nickName = jsonObject.getString("nickname");
        return new TextMessage(map, nickName + "谢谢关注");
    }

    /**
     * 处理位置信息
     *
     * @param map
     * @return
     * @throws IOException
     */
    private static BaseMessage dealEventLocation(Map<String, String> map) throws IOException {
        log.info("【收到用户位置消息，纬度{}，经度{}，经度{}】", map.get("Latitude"), map.get("Longitude"), map.get("Longitude"));
        // 拿到地址
        // 根据经纬度获取地址
        String url = "http://api.map.baidu.com/geocoder/v2/?ak=pmCgmADsAsD9rEXkqWNcTzjd&location=address&output=json&pois=1";
        String address = map.get("Latitude") + "," + map.get("Longitude");
        url = url.replace("address", address);
        // 发送请求
        URL uRL = new URL(url);
        URLConnection urlConnection = uRL.openConnection();
        // 拿到输入流
        InputStream inputStream = urlConnection.getInputStream();
        int len = 0;
        StringBuilder builder = new StringBuilder();
        byte[] bytes = new byte[1024];
        while ((len = inputStream.read(bytes)) != -1) {
            builder.append(new String(bytes, 0, len));
        }
        System.out.println(builder.toString());
        return new TextMessage(map, "success");
    }

    /**
     * 处理图文信息
     *
     * @param map
     * @return
     */
    private static BaseMessage dealEventView(Map<String, String> map) {
        return new TextMessage(map, "点击图文类型");
    }

    /**
     * 处理菜单的点击事件信息
     *
     * @param map
     * @return
     */
    private static BaseMessage dealEventClick(Map<String, String> map) {
        // 绑定的事件编号
        String eventKey = map.get("EventKey");
        log.info("【eventKey是{}】", eventKey);
        switch (eventKey) {
            case "1":
                log.info("点击了第一个菜单");
                return new TextMessage(map, "点击了第一个菜单");
            case "32":
                log.info("点击了第三个的一级菜单的第二个子菜单");
                return new TextMessage(map, "点击了第三个的一级菜单的第二个子菜单");
            default:
                log.error("不支持的时间类型");
                break;
        }
        return new TextMessage(map, "不支持的事件类型");
    }

    /**
     * 处理连接类型数据
     *
     * @param map
     * @return
     */
    public static BaseMessage dealLink(Map<String, String> map) {
        // 拿到地址
        String url = map.get("Url");
        // 发送请求
        String content = HttpUtil.get(url);
        log.info("【链接内容】{}", content);
        return new TextMessage(map, content);
    }

    public static BaseMessage dealImageWithIdCard(Map<String, String> map) {
        log.info("【进入身份证识别接口了】");
        // 拿到图片地址
        String picUrl = map.get("PicUrl");
        // 拿到token
        TokenUtil tokenUtil = ApplicationContextHolder.getBean(TokenUtil.class);
        // 地址
        String url = "https://api.weixin.qq.com/cv/ocr/idcard?img_url=ENCODE_URL&access_token=ACCESS_TOCKEN";
        url = url.replace("ACCESS_TOCKEN", tokenUtil.getToken().getAccessToken()).replace("ENCODE_URL", picUrl);
        // 发送请求
        String result = HttpUtil.get(url);
        return new TextMessage(map, result);
    }
}
